package XMFramework.Core
{
	import flash.display.Loader;
	import flash.events.Event;
	import flash.events.EventDispatcher;
	import flash.events.IOErrorEvent;
	import flash.events.SecurityErrorEvent;
	import flash.net.URLRequest;
	import flash.system.LoaderContext;
	
	[event(name="SImageLoader_LOAD_COMPLETED", type="SImageLoader")]
	public class SImageLoader extends EventDispatcher
	{
		public static const LOAD_COMPLETED : String	=	 "SImageLoader_LOAD_COMPLETED";
		
		private var _url : String;
		private var loader : Loader;
		private var isLoaded : Boolean;
		
		private var callbackObj : Array	=	new Array();
		
		public function SImageLoader( url : String )
		{
			_url		=	url;					
			isLoaded	=	false;
			
			super();
		}
		
		public function getImage( func : Function, thisObject : * = null ) : void
		{
			if( isLoaded )
				func.call( thisObject, loader.content, _url );
			
			else
			{
				var obj : Object	=	new Object();
				obj					=	new Object();
				obj.target			=	func;
				obj.thisObject		=	thisObject;
				callbackObj.push( obj );
				
				loadImage();
			}
		}
				
		private function loadImage() : void
		{			
			if( isLoaded )
				return;
			try
			{
				if( loader )
				{					
					loader.close();					
					loader	=	null;
				}
				
				loader		=	new Loader();
				loader.contentLoaderInfo.addEventListener( Event.COMPLETE, onLoadComplete );
				loader.contentLoaderInfo.addEventListener( IOErrorEvent.IO_ERROR, onErrorHandler );
				loader.contentLoaderInfo.addEventListener( SecurityErrorEvent.SECURITY_ERROR, onSecurityError );
				
				var context : LoaderContext	=	new LoaderContext();
				context.checkPolicyFile		=	true;
				context.securityDomain		=	null;
				
				loader.load( new URLRequest( _url ), context );
			}
			catch(ex:*){}
		}
		
		private function onLoadComplete( evt : Event ) : void
		{
			try
			{
				// Check to see if content is loaded success
				if( evt.target.content != null )
				{
					isLoaded	=	true;
					
					for each( var obj : Object in callbackObj )
					{			
						if( obj.target != null )
						{
							try
							{
								obj.target.call( obj.thisObject, evt.target.content, _url );
							} 
							catch(e:*) {}
							
						}
					}
					
					callbackObj	=	new Array();
					dispatchEvent( new Event( LOAD_COMPLETED ) );
				}
				
				// Try to reload asset resource
				else
					loadImage();
			}
			catch(ex:*){}
		}
				
		private function onErrorHandler( evt:IOErrorEvent ) : void
		{
			trace( "SImageLoader::Image load failed: " + evt["text"] );	
			
			if( evt.errorID == 2036 ) // Error #2036: Load Never Completed. URL: http://...
				return;			
			
			isLoaded	=	false;
			loadImage();
		}
		
		private function onSecurityError( evt : SecurityErrorEvent ) : void
		{
			trace( "SImageLoader::Image load security error: " + evt.text );
			
			// Retry to download resource
			isLoaded	=	false;
			loadImage();
		}
	}
}